<template>
	<view class="chat-wrapper">
		<scroll-view class="chat-messages" scroll-y="true" :scroll-into-view="scrollToView">
			<view class="message-item" v-for="(item, index) in msgList" :key="item.id" :id="'msg-' + item.id"
				:class="{ 'other-message': item.fromUser !== loginUserId, 'my-message': item.fromUser === loginUserId }">
				<!-- 撤回通知文本 -->
				<template v-if="item.type === 'withdraw'">
					<view class="withdraw-notification">
						<text>{{ item.text }}</text>
					</view>
				</template>
				<!-- 对方消息 -->
				<template v-else-if="item.fromUser !== loginUserId">
					<image class="avatar other-avatar" :src="avatarUrl1" mode="aspectFill"></image>
					<view class="message-bubble other-bubble">
						<text class="message-text" v-if="!item.voicePath">{{ item.text }}</text>
						<view v-if="item.voicePath" @click="playVoice(item)">
							<text class="voice-length">{{ Math.floor(item.voiceDuration) }}''</text>
							<image class="voice-icon"
								:src="playStatus === item.id ? '/static/icon/播放.png' : '/static/icon/语音.png'"
								mode="aspectFit"></image>
							<progress :percent="item.progress" border-radius="10" color="green" stroke-width="10"
								backgroundColor="#fff" />
						</view>
					</view>
				</template>
				<!-- 自己消息 -->
				<template v-else>
					<view class="message-bubble my-bubble" @longpress="showWithdraw(index)">
						<text class="message-text" v-if="!item.voicePath">{{ item.text }}</text>
						<view v-if="item.voicePath" @click="playVoice(item)">
							<text class="voice-length">{{ Math.floor(item.voiceDuration) }}''</text>
							<image class="voice-icon"
								:src="playStatus === item.id ? '/static/icon/播放.png' : '/static/icon/发语音.png'"
								mode="aspectFit"></image>
						</view>
						<view v-if="showWithdrawButton[index]" class="withdraw-container"
							@click.stop="withdrawMessage(item, index)">
							<text style="color: #ff0000; cursor: pointer;">撤回</text>
						</view>
					</view>
					<image class="avatar my-avatar" :src="avatarUrl" mode="aspectFill"
						style="width: 45px; height: 45px; border-radius: 50%; margin-left: 15px;"></image>
				</template>
			</view>
		</scroll-view>
		<!-- 输入区域 -->
		<view class="input-area" style="display: flex; align-items: center;">
			<!-- 切换按钮 后面会用到 -->
			<!-- 	<image v-if="!isRecording" class="toggle-button" @click="toggleInputMode"
				:src="isTextMode? '/static/icon/按住说话中.png' : '/static/icon/键盘.png'" mode="aspectFit"></image> -->
			<image v-if="!isRecording" class="toggle-button" :src="'/static/icon/键盘.png'" mode="aspectFit"></image>
			<view class="input-box-wrapper" v-if="isTextMode">
				<input v-model="content" class="input-box" hold-keyboard=true placeholder="请输入内容" ref="inputBox"
					cursor-spacing=25px @confirm="send"></input>
			</view>
			<view class="input-box-wrapper" v-else>

				<!-- 显示“按住说话”文本 -->
				<input v-if="!isRecording" @touchstart.prevent="startRecord" @touchend.prevent="endRecord"
					class="input-box" placeholder="按住说话" ref="inputBox" disabled></input>

				<!-- 显示播放图标 -->
				<img v-if="isRecording" src="/static/icon/播放.png" style="margin-left: 10px;" />
				<view v-if="isRecording" class="recording-animation"></view>
			</view>
			<image v-if="!isRecording" class="toggle-button" @click="send" :src="'/static/icon/发送.png'"
				mode="aspectFit">

			</image>
		</view>
		<!-- 语音预览区域 后面会用到-->
		<!-- <view v-if="voicePath" class="voice-preview">
			<button class="send-button" @click="sendVoice">发送语音</button>
			<image class="voice-icon" src="/static/icon/语音.png" mode="aspectFit" >
			</image>
			<button class="cancel-button" @click="cancelVoice">取消</button>
		</view> -->

		<!-- 输入模式提示区域 后面会用到-->
		<!-- <view v-if="showInputTip" class="input-tip"
			style="background-color: rgba(0, 0, 0, 0.5); color: #fff; padding: 12px; position: fixed; bottom: 60px; left: 50%; transform: translateX(-50%); border-radius: 8px;">
			<text v-if="isTextMode">文字输入模式</text>
			<text v-if="!isTextMode">语音输入模式</text>
		</view> -->
	</view>
</template>

<script>
	import request from '@/util/request';
	import Vue from 'vue';
	const recorderManager = uni.getRecorderManager();
	const innerAudioContext = uni.createInnerAudioContext();
	//检测长按事件
	Vue.directive('longpress', {
		bind(el, binding) {
			let start = null;
			el.addEventListener('touchstart', () => {
				start = new Date();
			});
			el.addEventListener('touchend', () => {
				const end = new Date();
				if (end - start >= 1000) {
					binding.value();
				}
			});
		}
	});

	export default {
		data() {
			return {
				loginUserId: '',
				recipientID: '',
				avatarUrl1:'../../static/icon/默认头像.jpg',//商家头像
				avatarUrl:'../../static/icon/默认头像.jpg',//用户头像
				content: '',
				msgList: [],
				isRecording: false,
				voicePath: '',
				status: 0,
				playStatus: 0,
				scrollToView: '',
				socketOpen: false,
				socketMsgQueue: [],
				time: 1,
				recordedVoice: null,
				isTextMode: true,
				showInputTip: false,
				showWithdrawButton: [],
				messageSendTimes: {},
				read: false,
				heartbeatInterval: 10000,
				heartbeatTimer: null,
				lastHeartbeatTime: 0,
				heartbeatCheckInterval: null,
				reconnectAttempts: 0,
				maxReconnectAttempts: 5,
				isReconnecting: false, // 新增标识是否正在重连
				isMerchant: false, // 是否是商家
				isMerchantPhone: '',
				loginUser:{},
				wb:"wss://absolutuniq.com:8088/imserver"
				//wb:"ws://127.0.0.1:8088/imserver"
			};
		},
		onHide() {
			this.stopHeartbeat();
			console.log("关闭连接");
			//uni.closeSocket();
			this.saveSocketMsgQueueToLocal();
		//	clearInterval(this.heartbeatCheckInterval);
		},
	  onLoad() {
		  	this.loginUser =  uni.getStorageSync("loginUser")
			this.loginUserId = this.loginUser.phone
			console.log(this.loginUser)
			if(this.loginUser.avatarUrl){
				this.avatarUrl = this.$baseUrl + this.loginUser.avatarUrl
			} 
			this.getMerchant()
			this.initWithdrawButtons();
			//this.startHeartbeatCheck(); //每分钟检查心跳包
			this.scrollToBottom(); // 发送消息在滚到到最新
			this.loadSocketMsgQueueFromLocal(); // 获取离线消息
			this.connectWebSocket(); // 连接
			this.locality()//查询本地历史记录
		//	this.IsLogin(this.recipientID)//查询对面头像
		},
		methods: {
			getMerchant() {
				this.$myRequest({
					url: '/about/query',
					method: 'GET',
					}).then(res =>{
						this.recipientID = res.data.phone;
						 request({
						 	url: '/users/getUserAvatarUrl',
						 	method: 'get',
						 	data: {
						 		userId: res.data.phone
						 	}
						 }).then(res => {
							 if(res.msg){
								this.avatarUrl1 = this.$baseUrl+res.msg //用户
							 } 
						 	
						 }).catch(err => {
						 	console.error('获取用户信息失败：', err);
						 	// 可以根据具体情况进行更合适的错误处理，比如设置默认值、提示用户等
						 });
						
					})
			},
			connectWebSocket() {
				console.log(this.loginUser)
				uni.connectSocket({
					url: this.$wbBaseUrl +  '/'+this.loginUser.phone+'/read'
				});
				uni.onSocketOpen(() => {
					this.socketOpen = true;
					//this.startHeartbeat();
					console.log("连接成功");
					this.reconnectAttempts = 0;
					// 发送之前存储的离线消息
					this.socketMsgQueue.forEach(msg => this.sendSocketMessage(msg));
					this.socketMsgQueue = []; // 清空消息队列
				});

				uni.onSocketMessage((res) => {
					console.log('收到服务器内容：' + res.data);
					if (res.data === 'heartbeat') {
						this.lastHeartbeatTime = Date.now();
						return;
					}
					const message = JSON.parse(res.data);
					if (message.recall) {
						this.withdrawMessage(message);
					} else if (message.type === 'messageWithdrawn') {
						this.handleMessageWithdrawnNotification(message.messageId);
					} else {
						message.voiceDuration = message.voiceDuration || 0;
						this.msgList.push(message);
						this.showWithdrawButton.push(false);
						if (message.fromUser === this.loginUserId) {
							this.messageSendTimes[message.id] = Date.now();
						}
						this.saveMessagesToStorage();
						this.scrollToBottom();
					}
				});

				uni.onSocketClose(() => {
					this.socketOpen = false
					console.log('WebSocket连接已关闭，准备重连...');
					//this.stopHeartbeat();
					//this.reconnectWebSocket();
				});

				uni.onSocketError(() => {
					this.socketOpen = false
					console.log('WebSocket连接发生错误，准备重连...');
					//this.stopHeartbeat();
				//	this.reconnectWebSocket();
				});
			},
			locality(){
				// 读取本地历史消息
				const storageKey = `chatData_${this.loginUserId}`;
				
				uni.getStorage({
					key: storageKey,
					success: res => {
						if (res.data) {
							this.msgList = res.data.filter((item, index, self) => {
								return self.findIndex((i) => i.id === item.id) === index && (item
									.fromUser === this.loginUserId || item.fromUser === this
									.recipientID);
							});
							this.initMessageTimes();
							this.initWithdrawButtons();
						} else {
							console.log('读取本地存储失败，没有数据');
						}
					},
					fail: (err) => {
						console.log('读取本地存储失败', err);
					}
				});
			},
			async getPhone() {
					//获取电话
					this.getUserPhone();
					request({
						url: '/about/query',
						method: 'GET',
					}).then(res => {
						this.aboutInfo = res;
						this.recipientID=this.aboutInfo.data.phone; //商家
						this.isMerchant = this.loginUserId === this.aboutInfo.data.phone; //商家
					})
				},
			async getUserPhone() {
				const systemInfo = uni.getSystemInfoSync(); 
					this.userId = systemInfo.deviceId;
				
				const isLogin = uni.getStorageSync("isLogin")
				console.log(isLogin)
				if (isLogin) {
					request({
						url: '/users/',
						method: 'get',
						data: {
							userId: this.userId
						}
					}).then(res => {
						console.log(res.data)
						this.loginUserId = res.data.phone//用户
						this.locality();
				
					})
				}
			},
			// 获取对面的头像
			IsLogin(userId) {
				request({
					url: '/users/getUserAvatarUrl',
					method: 'get',
					data: {
						userId: userId
					}
				}).then(res => {
					this.avatarUrl1 = this.$baseUrl+res.msg //用户
				}).catch(err => {
					console.error('获取用户信息失败：', err);
					// 可以根据具体情况进行更合适的错误处理，比如设置默认值、提示用户等
				});
			},
			getAvatar(userId) {
				if (userId === "18640966675") {
					return this.avatarUrl1;
				}
				return this.avatarUrl;
			},	
			//检查心跳包逻辑
			checkHeartbeatTimeout() {
				const HEARTBEAT_TIMEOUT = 60 * 1000;
				if (Date.now() - this.lastHeartbeatTime > HEARTBEAT_TIMEOUT) {
					console.log('心跳包超时，准备重连...');
					this.socketOpen = false
					this.reconnectWebSocket();
				} else {
					console.log("心跳包正常");
				}
			},
			//每分钟检查心跳包
			startHeartbeatCheck() {
				this.heartbeatCheckInterval = setInterval(() => {
					this.checkHeartbeatTimeout();
				}, 5000);
			},
			// 开始发送心跳包
			startHeartbeat() {
				if (!this.heartbeatTimer) {
					this.heartbeatTimer = setInterval(() => {
						if (this.socketOpen) {
							
							console.log('发送心跳包用户');
							uni.sendSocketMessage({
								data: 'heartbeat'
							});
						}
					}, this.heartbeatInterval);
				}
			},
			// 停止心跳包
			stopHeartbeat() {
				
				if (this.heartbeatTimer) {
					clearInterval(this.heartbeatTimer);
					this.heartbeatTimer = null;
				}
			},
			reconnectWebSocket() {
				if (this.isReconnecting) {
					console.log('已经在重连中，忽略本次重连请求');
					return;
				}
				this.isReconnecting = true;
				if (this.reconnectAttempts >= this.maxReconnectAttempts) {
					console.log('重连次数超过最大限制，停止重连');
					uni.showToast({
						title: '连接出现问题，请检查网络或稍后再试',
						icon: 'none'
					});
					this.saveSocketMsgQueueToLocal(); // 保存消息队列到本地存储

					const currentPage = getCurrentPages().pop(); // 获取当前页面实例
					if (currentPage) {
						uni.reLaunch({
							url: currentPage.route // 重新加载当前页面
						});
					}

				} else {
					this.stopHeartbeat();
					this.reconnectAttempts++;
					const delay = Math.min(5000 * Math.pow(2, this.reconnectAttempts - 1), 60000);
					const randomDelay = Math.random() * 1000;
					setTimeout(() => {
						this.connectWebSocket();
						console.log('正在重连...');
						this.isReconnecting = false;
					}, delay + randomDelay);
				}
			},
			
			initMessageTimes() {
				this.msgList.forEach(item => {
					if (item.fromUser === this.loginUserId && !this.messageSendTimes[item.id]) {
						this.messageSendTimes[item.id] = item.sendTime || Date.now();
					}
				});
			},
			handleMessageWithdrawnNotification(messageId) {
				this.msgList = this.msgList.map(item => {
					if (item.id === messageId) {
						item.isWithdrawn = true;
						this.$forceUpdate();
					}
					return item;
				});
			},
			initWithdrawButtons() {
				this.showWithdrawButton = this.msgList.map(() => false);
			},
			// 存储离线消息
			saveMessagesToStorage() {
				const storageKey = `chatData_${this.loginUserId}`;
				uni.setStorage({
					key: storageKey,
					data: this.msgList,
					success: () => {
						console.log('消息列表更新并存储成功');
					},
					fail: (err) => {
						console.log('消息列表存储失败', err);
					}
				});
			},
			send() {
				const msg = {
					text: this.content.trim(),
					fromUser: this.loginUser.phone,
					id: Date.now(),
					sendTime: Date.now(),
					type: 'text',
					recipientID: this.recipientID,//this.recipientID
				};
				console.log(msg)
				console.log(this.loginUser)
				if (msg.text) {
					this.msgList.push(msg);
					this.content = '';
					this.sendSocketMessage(msg);
					this.saveMessagesToStorage();
					this.scrollToBottom();
				}
			},
			sendSocketMessage(msg) {
				return new Promise((resolve, reject) => {
					if (this.socketOpen) {
						uni.sendSocketMessage({
							data: JSON.stringify(msg),
							success: () => {
								resolve();
								console.log('消息发送成功');
							},
							fail: (err) => {
								console.error('消息发送失败', err);
								this.socketMsgQueue.unshift(msg);
								reject(err);
							}
						});
					} else {

						console.log('WebSocket未连接，将消息添加到队列，消息内容：', msg);
						this.socketMsgQueue.push(msg);
						this.stopHeartbeat();
						this.reconnectWebSocket();
						resolve();
					}
				});
			},
			startRecord() {
				clearInterval(this.init);
				this.time = 1;
				this.status = 1;
				this.isRecording = true;
				this.recordedVoice = null;
				recorderManager.start({
					duration: 60000,
					sampleRate: 16000,
					numberOfChannels: 1,
					encodeBitRate: 96000,
					format: 'mp3',
					frameSize: 10,
					onError: (res) => {
						console.error('录音失败', res);
						uni.showToast({
							title: '录音失败，请检查您的麦克风权限',
							icon: 'none'
						});
					}
				});
				recorderManager.onStop((res) => {
					console.log('recorder stop', res);
					this.voicePath = res.tempFilePath;
					this.status = 3;
					this.recordedVoice = res.tempFilePath;
					this.updateTime(res.duration);
					const voiceDuration = this.time;
					if (this.recordedVoice) {
						const lastMessage = this.msgList[this.msgList.length - 1];
						if (lastMessage && lastMessage.type === 'voice') {
							lastMessage.voiceDuration = voiceDuration;
						}
					}
				});
				this.recordingTimer();
			},
			endRecord() {
				this.isRecording = false;
				recorderManager.stop();
			},
			sendVoiceMessage() {
				const msg = {
					voicePath: this.voicePath,
					fromUser: this.loginUserId,
					id: Date.now(),
					progress: 0,
					sendTime: Date.now(),
					type: 'voice',
					voiceDuration: this.time,
				};
				if (this.voicePath) {
					this.msgList.push(msg);
					this.voicePath = '';
					this.sendSocketMessage(msg);
					this.saveMessagesToStorage();
					this.scrollToBottom();
					this.resetVoice();
				}
			},
			playVoice(item) {
				if (item.voicePath) {
					if (this.playStatus && this.playStatus !== item.id) {
						innerAudioContext.stop();
					}
					innerAudioContext.src = item.voicePath;
					innerAudioContext.onPlay(() => {
						this.playStatus = item.id;
						this.updateProgress(item);
					});
					innerAudioContext.onError((err) => {
						console.error('播放错误', err);
					});
					innerAudioContext.onEnded(() => {
						this.playStatus = 0;
						item.progress = 0;
					});
					innerAudioContext.play();
				}
			},
			recordingTimer() {
				this.init = setInterval(() => {
					this.time += 1;
					if (this.time >= 60) {
						this.endRecord();
					}
				}, 1000);
			},
			updateTime(duration) {
				this.time = Math.min(duration / 1000, 60);
			},
			updateProgress(item) {
				const duration = innerAudioContext.duration;
				const intervalId = setInterval(() => {
					if (innerAudioContext.paused || innerAudioContext.ended) {
						clearInterval(intervalId);
						return;
					}
					const currentTime = innerAudioContext.currentTime;
					item.progress = (currentTime / duration) * 100;
				}, 1000);
			},
			// 发送消息在滚到到最新
			scrollToBottom() {
				this.$nextTick(() => {
					const newMessageId = 'msg-' + this.msgList[this.msgList.length - 1].id;
					this.scrollToView = newMessageId;
				});
			},
			sendVoice() {
				if (this.recordedVoice) {
					const msg = {
						voicePath: this.recordedVoice,
						fromUser: this.loginUserId,
						id: Date.now(),
						progress: 0,
						sendTime: Date.now(),
						type: 'voice',
						voiceDuration: this.time,
					};
					this.msgList.push(msg);
					this.sendSocketMessage(msg);
					this.saveMessagesToStorage();
					this.scrollToBottom();
					this.resetVoice();
				}
			},
			cancelVoice() {
				this.resetVoice();
			},
			resetVoice() {
				this.voicePath = '';
				this.recordedVoice = null;
				this.time = 0;
				this.isRecording = false;
			},
			toggleInputMode() {
				this.isTextMode = !this.isTextMode;
				this.showInputTip = true;
				setTimeout(() => {
					this.showInputTip = false;
				}, 2000);
			},
			isWithdrawable(item) {
				if (item.time) {
					return item.time - item.sendTime <= 120 * 1000;
				} else {
					const currentTime = Date.now();
					return currentTime - item.sendTime <= 120 * 1000;
				}
			},
			showWithdraw(index) {
				this.$set(this.showWithdrawButton, index, true);
			},
			withdrawMessage(messageId) {
				const index = this.msgList.findIndex(item => item.id === messageId.id);
				if (index !== -1) {
					const item = messageId;
					if (this.isWithdrawable(messageId)) {
						const originalPosition = {
							fromUser: item.fromUser,
							isMyMessage: item.fromUser === this.loginUserId,
							marginTop: this.$refs[`message - $ {
								index
							}`] ? this.$refs[`message - $ {
								index
							}`].$el.style.marginTop : '',
							marginBottom: this.$refs[`message - $ {
								index
							}`] ? this.$refs[`message - $ {
								index
							}`].$el.style.marginBottom : '',
							marginLeft: this.$refs[`message - $ {
								index
							}`] ? this.$refs[`message - $ {
								index
							}`].$el.style.marginLeft : '',
							marginRight: this.$refs[`message - $ {
								index
							}`] ? this.$refs[`message - $ {
								index
							}`].$el.style.marginRight : ''
						};
						this.msgList.splice(index, 1);
						let withdrawNotificationText;
						if (item.fromUser === this.loginUserId) {
							withdrawNotificationText = '你撤回了一条消息';
							this.sendWithdrawNotificationToServer(messageId);
						} else {
							withdrawNotificationText = '对方撤回了一条消息';
						}
						const withdrawNotification = {
							text: withdrawNotificationText,
							fromUser: item.fromUser === this.loginUserId ? this.loginUserId : '对方',
							id: item.id,
							sendTime: Date.now(),
							type: 'withdraw',
							isWithdrawNotification: true,
						};
						this.msgList.splice(index, 0, withdrawNotification);
						this.$nextTick(() => {
							if (originalPosition.isMyMessage) {
								this.$refs[`message - $ {
									index
								}`].$el.style.marginRight = originalPosition.marginRight;
							} else {
								this.$refs[`message - $ {
									index
								}`].$el.style.marginLeft = originalPosition.marginLeft;
							}
						});
						this.saveMessagesToStorage();
					} else {
						uni.showToast({
							title: '消息已经发送超过两分钟，不可撤回',
							icon: 'none'
						});
					}
				}
			},
			sendWithdrawNotificationToServer(messageId) {
				messageId = {
					...messageId,
					recall: true,
					time: Date.now()
				};
				this.sendSocketMessage(messageId);
			},
			//存储离线消息
			saveSocketMsgQueueToLocal() {
				const storageKey = this.loginUserId;
				uni.setStorage({
					key: storageKey,
					data: this.socketMsgQueue,
					success: () => {
						console.log('消息队列保存到本地存储成功');
					},
					fail: (err) => {
						console.log('消息队列保存到本地存储失败', err);
					}
				});
			},
			// 获取离线消息
			loadSocketMsgQueueFromLocal() {
				const storageKey = this.loginUserId;
				uni.getStorage({
					key: storageKey,
					success: (res) => {
						if (res.data) {
							this.socketMsgQueue = res.data;
							res.data.length = 0; // 直接清空数组
							console.log('从本地存储恢复消息队列成功');
						}
					},
					fail: () => {
						console.log('从本地存储恢复消息队列失败');
					}
				});
			},
		},
		beforeDestroy() {
			clearInterval(this.init);
			uni.closeSocket();
			clearInterval(this.heartbeatCheckInterval);
		}
	};
</script>

<style>
	/* 聊天文字样式 */
	.message-text {
		font-size: 18px;
		color: #333;
		padding: 12px;
		border-radius: 18px;
	}

	.chat-wrapper {
		background-color: #f8f8f8;
		display: flex;
		flex-direction: column;
		height: 100vh;
		background-color: #f8f8f8;
		font-family: 'Arial', sans-serif;
		/* 设置字体 */
		overflow: hidden;
		/* 防止内容溢出 */
	}

	.chat-header {
		padding: 15px;
		font-size: 22px;
		font-weight: bold;
		border-bottom: 2px solid #ddd;
		background-color: #e0e0e0;
		color: #333;
		text-align: center;
		/* 居中标题 */
		box-shadow: 0 2px 5px rgba(0, 0, 0, 0.1);
		/* 添加阴影 */
	}

	.chat-messages {
		flex-grow: 1;
		overflow-y: auto;
		padding: 10px;
		background-color: #238dff;
		/* 圆角边框 */
		border-radius: 0px;
		/* 添加阴影 */
		box-shadow: 0 4px 8px rgba(0, 0, 0, 0.1);

	}

	.message-item {
		display: flex;
		margin-bottom: 8px;
		align-items: center;
		/* 垂直居中 */
		animation: fadeIn 0.5s ease-in-out;
		/* 添加淡入动画 */
	}

	.other-message {
		justify-content: flex-start;
	}

	.my-message {
		justify-content: flex-end;
		margin-right: 25px;
	}

	.message-container {
		display: flex;
		align-items: flex-start;
	}

	.avatar-container {
		width: 60px;
		display: flex;
		justify-content: center;
		align-items: center;
		margin-right: 10px;
	}

	.avatar {
		margin-right: 15px;
		width: 45px;
		height: 45px;
		border-radius: 50%;
		border: 2px solid #fff;
		/* 头像边框 */
		box-shadow: 0 2px 5px rgba(0, 0, 0, 0.2);

	}

	.message-bubble {
		background-color: #b3e5fc;
		position: relative;
		padding: 12px;
		border-radius: 18px;
		word-wrap: break-word;
		font-size: 16px;
		background-color: #eaeaea;
		/* 默认气泡颜色 */
		box-shadow: 0 2px 5px rgba(0, 0, 0, 0.15);
		/* 气泡阴影 */
		max-width: 75%;
		/* 限制气泡宽度 */
	}

	.other-bubble {
		background-color: #eaeaea;
		margin-bottom: 10px;
		margin-right: 20px;
	}

	.my-bubble {
		background-color: #b3e5fc;
		margin-bottom: 10px;
		margin-left: 20px;
	}

	.input-area {
		display: flex;
		align-items: center;
		padding: 12px;
		border-top: 1px solid #ddd;
		background-color: #ffffff;


	}

	.input-box {
		flex-grow: 1;
		padding: 12px;
		border-radius: 25px;
		border: 1px solid #ddd;
		margin: 0 12px;
		font-size: 18px;
		caret-color: #007aff;
		text-align: center;
		/* 尝试使用text-align来居中文本 */
	}

	.button-group {
		display: flex;
		align-items: center;
	}

	.send-button {
		/* 增加字体大小 */
		cursor: pointer;
		/* 鼠标悬停时显示指针 */
		transition: background-color 0.3s ease;
		background-color: #1AAD19;
		color: #fff;
		border: none;
		border-radius: 25px;
		padding: 12px 25px;
		font-size: 10px;
		cursor: pointer;
	}

	.record-button {
		background-color: #eaeaea;
		color: #ffffff;
		border-radius: 4px;
		margin-left: 10px;
		padding: 10px 20px;
		/* 增加按钮大小 */
		font-size: 16px;
		/* 增加字体大小 */
		cursor: pointer;
		/* 鼠标悬停时显示指针 */

	}

	.voice-preview {
		display: flex;
		align-items: center;
		justify-content: space-between;
		padding: 18px;
		border-radius: 8px;
		/* 圆角边框 */
		box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
		/* 添加阴影 */
		background-color: #f0f0f0;
		/* 背景颜色 */
	}

	.voice-icon {
		width: 35px;
		height: 27px;

	}

	.voice-length {
		font-size: 18px;
		color: #666;
	}

	/*  取消*/
	.cancel-button {
		transition: background-color 0.3s ease;
		background-color: #ddd;
		color: #666;
		border: none;
		border-radius: 25px;
		padding: 12px 25px;
		font-size: 13px;
		cursor: pointer;
	}

	.input-tip {
		display: flex;
		align-items: center;
		justify-content: center;
		background-color: rgba(0, 0, 0, 0.5);
		color: #fff;
		padding: 12px;
		position: fixed;
		bottom: 60px;
		left: 50%;
		transform: translateX(-50%);
		border-radius: 10px;
		z-index: 10;
		/* 确保提示显示在顶层 */
	}

	.withdraw-container {
		position: absolute;
		top: -5px;
		right: -5px;
		background-color: rgba(255, 0, 0, 0.5);
		color: #ffffff;
		border-radius: 15px;
		padding: 5px 10px;
		font-size: 14px;
		cursor: pointer;
		display: none;
	}

	.my-bubble:hover .withdraw-container {
		display: block;
	}

	.withdraw-message {
		text-align: center;
		font-size: 14px;
		color: #888;
		margin-top: 5px;
	}

	.withdraw-notification {
		text-align: center;
		padding: 10px;
		margin-top: 5px;
		margin-bottom: 5px;
		margin-left: auto;
		margin-right: auto;
		color: #888;
		font-size: 14px;
	}

	.toggle-button {
		width: 45px;
		height: 45px;
	}

	.input-box-wrapper {
		flex-grow: 1;
		margin: 0 10px;
		display: flex;
		align-items: center;
		/* 垂直居中对齐 */
	}
</style>